﻿using HDSmartCommunity.BUS;
using HDSmartCommunity.DAL;
using HDSmartCommunity.DevicePlatform;
using HDSmartCommunity.Models;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Caching.Memory;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.NetworkInformation;
using System.Net.Sockets;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading;
using System.Threading.Tasks;
using System.Timers;

namespace HDSmartCommunity.HDPlatform
{
    public class HDProcessData
    {
        public Socket server;
        public Thread thread;
        public int count = 1;//流水号
        public string devid;//主设备ID
        public string subdevid;//子设备ID
        public Dictionary<int, List<byte>> dic_data = new Dictionary<int, List<byte>>();
        public static MemoryCache memoryCache = new MemoryCache(new MemoryCacheOptions() { });
        public DevInfo devinfo;
        public static ParameterRead Parameter = new ParameterRead();
        public DeviceSerialData serial;
        public static object sendlocker = new object();
        public static object carstatuslocker = new object();
        public int heartcount = 0;
        public static CancellationTokenSource tokenSource = new CancellationTokenSource();
        public CancellationToken token = tokenSource.Token;
        public ManualResetEvent resetEvent = new ManualResetEvent(true);
        public static int hdstatus = 0;//金茂平台连接状态，1：注册中，2：心跳发送中
        System.Timers.Timer t;
        private static bool isReg = false;
        private static bool firstReg = true;
        public LogPrint logPrint;
        public int reporttime = 0;
        System.Timers.Timer reporttimer = null;
        public bool isreport = false;
        public static ElevatorStatusInfo ElevatorStatusInfo = new ElevatorStatusInfo();
        public string ip;
        public int interval;

        public static CancellationTokenSource visit_tokenSource = new CancellationTokenSource();
        public CancellationToken visit_token = visit_tokenSource.Token;
        public ManualResetEvent visit_resetEvent = new ManualResetEvent(true);

        public string StringToHex(string strEncode)
        {
            string strReturn = "";
            foreach (short shortx in strEncode.ToCharArray())
            {
                strReturn += shortx.ToString("X2") + " ";
            }
            strReturn = strReturn.TrimEnd(' ').ToUpper();
            return strReturn;
        }

        public string IntToHex(int num)
        {
            string result = "";
            result = Convert.ToString(num, 16).ToUpper();
            return result;
        }

        #region 连接金茂服务器

        public bool ConnectServer(string serverIP, int port)
        {
            try
            {
                server = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                //server.Connect("192.168.8.100", 20003);
                server.Connect(serverIP, port);
                //server.ReceiveTimeout = 10000;
                thread = new Thread(StartReceive);
                thread.Start(server);
                return true;
            }
            catch (Exception e)
            {
                // logPrint.Log("连接金茂异常");
                return false;
            }
        }

        #endregion
        List<byte> TmpDataReceived = new List<byte>();
        #region 接收金茂平台消息
        public void VISIT_CONTROL(string data, string DeviceID)
        {
            try
            {
                Task task = new Task(async () =>
                {
                    if (visit_token.IsCancellationRequested)
                    {
                        return;
                    }
                    visit_resetEvent.WaitOne();
                    //do something
                    ReturnVisitControl returnVisitControl = new ReturnVisitControl();
                    string strCmd = string.Empty;
                    string str = string.Empty;
                    DateTime startTime;
                    try
                    {
                        VisitControl visitControl = GetVisitControl(data);
                        CurrentElevatorStatus currentElevatorStatus = new CurrentElevatorStatus();
                        serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                        if (currentElevatorStatus.Fault == 0)
                        {
                            List<string> showlist = serial.show_list;
                            List<int> phylist = serial.phy_list;
                            int SrcFloor_phy = 0;
                            for (int i = 0; i < showlist.Count; i++)
                            {
                                if (showlist[i] == visitControl.SrcFloor)
                                {
                                    SrcFloor_phy = phylist[i];
                                }
                            }
                            int DstFloor_phy = 0;
                            for (int i = 0; i < showlist.Count; i++)
                            {
                                if (showlist[i] == visitControl.DstFloor)
                                {
                                    DstFloor_phy = phylist[i];
                                }
                            }
                            serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                            string cmd = string.Empty;
                            bool wh_result;
                            if (currentElevatorStatus.Fault == 1)
                            {
                                returnVisitControl.Command = "KYL_VISIT_CONTROL";
                                returnVisitControl.DeviceID = DeviceID;
                                returnVisitControl.Seq = 1;
                                returnVisitControl.Signature = "";
                                returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                returnVisitControl.Result = 1;
                            }
                            else
                            {
                                if (SrcFloor_phy < DstFloor_phy)//外呼上行
                                {
                                    int add;
                                    if (visitControl.SrcSide == "0")//前门
                                    {
                                        cmd = Floor(1, 36, 1, SrcFloor_phy, out add);

                                    }
                                    else//后门
                                    {
                                        cmd = Floor(1, 46, 1, SrcFloor_phy, out add);
                                    }
                                    wh_result = serial.SendCmdToJM(cmd, 1, add, 1);
                                    //LogHelper.Log("外呼命令：" + cmd);
                                }
                                else//外呼下行
                                {
                                    int add;
                                    if (visitControl.SrcSide == "0")//前门
                                    {
                                        cmd = Floor(1, 41, 1, SrcFloor_phy, out add);

                                    }
                                    else//后门
                                    {
                                        cmd = Floor(1, 51, 1, SrcFloor_phy, out add);
                                    }
                                    //LogHelper.Log("外呼命令：" + cmd);
                                    wh_result = serial.SendCmdToJM(cmd, 1, add, 1);
                                }
                                if (wh_result)
                                {
                                    startTime = DateTime.Now;
                                    bool fault = false;
                                    bool delay = false;
                                    //当前楼层与源楼层一致时，且开门，内呼点亮
                                    while (!(visitControl.SrcFloor == currentElevatorStatus.DisplayFloor && currentElevatorStatus.Open == 1))
                                    {
                                        TimeSpan secondSpan = new TimeSpan(DateTime.Now.Ticks - startTime.Ticks);
                                        if (secondSpan.TotalSeconds > 600)
                                        {
                                            delay = true;
                                            break;
                                        }
                                        serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                                        if (currentElevatorStatus.Fault == 1)
                                        {
                                            fault = true;
                                            break;
                                        }
                                        continue;
                                    }
                                    if (fault)
                                    {
                                        returnVisitControl.Command = "KYL_VISIT_CONTROL";
                                        returnVisitControl.DeviceID = DeviceID;
                                        returnVisitControl.Seq = 1;
                                        returnVisitControl.Signature = "";
                                        returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                    }
                                    else
                                    {
                                        if (delay)
                                        {
                                            LogHelper.Log(data + "------命令超时");
                                        }
                                        else
                                        {
                                            int add_nh;
                                            if (visitControl.DstSide == "0")//前门
                                            {
                                                cmd = Floor(1, 26, 1, DstFloor_phy, out add_nh);
                                            }
                                            else//后门
                                            {
                                                cmd = Floor(1, 31, 1, DstFloor_phy, out add_nh);
                                            }
                                            LogHelper.Log("内呼点亮命令：" + cmd);
                                            bool dl_result = serial.SendCmdToJM(cmd, 1, add_nh, 1);
                                            returnVisitControl.Command = "KYL_VISIT_CONTROL";
                                            returnVisitControl.DeviceID = DeviceID;
                                            returnVisitControl.Seq = 1;
                                            returnVisitControl.Signature = "";
                                            returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                            if (dl_result)
                                            {
                                                returnVisitControl.Result = 0;
                                            }
                                            else
                                            {
                                                returnVisitControl.Result = 1;
                                            }
                                        }

                                    }
                                }
                                else
                                {
                                    LogHelper.Log(data + "外呼失败");
                                    returnVisitControl.Command = "KYL_VISIT_CONTROL";
                                    returnVisitControl.DeviceID = DeviceID;
                                    returnVisitControl.Seq = 1;
                                    returnVisitControl.Signature = "";
                                    returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                    returnVisitControl.Result = 1;
                                }
                            }
                        }
                        else
                        {
                            returnVisitControl.Command = "KYL_VISIT_CONTROL";
                            returnVisitControl.DeviceID = DeviceID;
                            returnVisitControl.Seq = 1;
                            returnVisitControl.Signature = "";
                            returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                            returnVisitControl.Result = 1;
                        }

                        str = JsonConvert.SerializeObject(returnVisitControl);
                        strCmd = StringToHex(str);
                    }
                    catch
                    {
                        returnVisitControl.Command = "KYL_VISIT_CONTROL";
                        returnVisitControl.DeviceID = DeviceID;
                        returnVisitControl.Seq = 1;
                        returnVisitControl.Signature = "";
                        returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                        returnVisitControl.Result = 1;
                        str = JsonConvert.SerializeObject(returnVisitControl);
                        strCmd = StringToHex(str);
                    }
                    SendMsg(strCmd, false, false);

                }, visit_token);
                task.Start();
            }
            catch (Exception e)
            {
                LogHelper.Log(e.ToString());
            }

        }
        public void KEY_CONTROL(string data, string DeviceID)
        {
            string strCmd = string.Empty;
            ReturnVisitControl returnVisitControl = new ReturnVisitControl();
            string str = string.Empty;
            DateTime startTime;
            try
            {
                CurrentElevatorStatus currentElevatorStatus = new CurrentElevatorStatus();
                serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                if (currentElevatorStatus.Fault == 1)
                {
                    returnVisitControl.Command = "KYL_KEY_CONTROL";
                    returnVisitControl.DeviceID = DeviceID;
                    returnVisitControl.Seq = 1;
                    returnVisitControl.Signature = "";
                    returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                    returnVisitControl.Result = 1;
                }
                else
                {
                    VisitControl visitControl = GetVisitControl(data);
                    List<string> showlist = serial.show_list;
                    List<int> phylist = serial.phy_list;
                    int SrcFloor_phy = 0;
                    for (int i = 0; i < showlist.Count; i++)
                    {
                        if (showlist[i] == visitControl.SrcFloor)
                        {
                            SrcFloor_phy = phylist[i];
                        }
                    }
                    int DstFloor_phy = 0;
                    for (int i = 0; i < showlist.Count; i++)
                    {
                        if (showlist[i] == visitControl.DstFloor)
                        {
                            DstFloor_phy = phylist[i];
                        }
                    }
                    serial.memoryCache.TryGetValue(1, out currentElevatorStatus);

                    string cmd = string.Empty;
                    bool wh_result;
                    if (SrcFloor_phy < DstFloor_phy)//外呼上行
                    {
                        int add;
                        if (visitControl.SrcSide == "0")//前门
                        {
                            cmd = Floor(1, 36, 1, SrcFloor_phy, out add);

                        }
                        else//后门
                        {
                            cmd = Floor(1, 46, 1, SrcFloor_phy, out add);
                        }
                        LogHelper.Log("外呼命令：" + cmd);
                        wh_result = serial.SendCmdToJM(cmd, 1, add, 1);
                    }
                    else//外呼下行
                    {
                        int add;
                        if (visitControl.SrcSide == "0")//前门
                        {
                            cmd = Floor(1, 41, 1, SrcFloor_phy, out add);

                        }
                        else//后门
                        {
                            cmd = Floor(1, 51, 1, SrcFloor_phy, out add);
                        }
                        //LogHelper.Log("外呼命令：" + cmd);
                        wh_result = serial.SendCmdToJM(cmd, 1, add, 1);
                    }
                    if (wh_result)
                    {
                        startTime = DateTime.Now;
                        //Thread.Sleep(interval);
                        bool fault = false;
                        bool delay = false;
                        //当前楼层与源楼层一致时，且开门，内呼授权
                        while (!(visitControl.SrcFloor == currentElevatorStatus.DisplayFloor && currentElevatorStatus.Open == 1))
                        {
                            TimeSpan secondSpan = new TimeSpan(DateTime.Now.Ticks - startTime.Ticks);
                            if (secondSpan.TotalSeconds > 600)
                            {
                                delay = true;
                                break;
                            }
                            serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                            if (currentElevatorStatus.Fault == 1)
                            {
                                fault = true;
                                break;
                            }
                            continue;
                        }
                        if (fault)
                        {
                            returnVisitControl.Command = "KYL_KEY_CONTROL";
                            returnVisitControl.DeviceID = DeviceID;
                            returnVisitControl.Seq = 1;
                            returnVisitControl.Signature = "";
                            returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                            returnVisitControl.Result = 1;

                        }
                        else
                        {
                            if (delay)
                            {
                                LogHelper.Log(data + "------命令超时");
                            }
                            else
                            {
                                int add_nh;
                                if (visitControl.DstSide == "0")//前门
                                {
                                    cmd = Floor(1, 16, 1, DstFloor_phy, out add_nh);
                                }
                                else//后门
                                {
                                    cmd = Floor(1, 21, 1, DstFloor_phy, out add_nh);
                                }
                                LogHelper.Log("内呼授权命令：" + cmd);
                                bool dl_result = serial.SendCmdToJM(cmd, 1, add_nh, 1);
                                returnVisitControl.Command = "KYL_KEY_CONTROL";
                                returnVisitControl.DeviceID = DeviceID;
                                returnVisitControl.Seq = 1;
                                returnVisitControl.Signature = "";
                                returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");

                                if (dl_result)
                                {
                                    returnVisitControl.Result = 0;
                                }
                                else
                                {
                                    returnVisitControl.Result = 1;
                                }
                            }
                        }
                    }
                    else
                    {
                        LogHelper.Log(data + "外呼失败");
                        returnVisitControl.Command = "KYL_KEY_CONTROL";
                        returnVisitControl.DeviceID = DeviceID;
                        returnVisitControl.Seq = 1;
                        returnVisitControl.Signature = "";
                        returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                        returnVisitControl.Result = 1;
                    }
                }

                str = JsonConvert.SerializeObject(returnVisitControl);
                strCmd = StringToHex(str);
            }
            catch
            {
                returnVisitControl.Command = "KYL_KEY_CONTROL";
                returnVisitControl.DeviceID = DeviceID;
                returnVisitControl.Seq = 1;
                returnVisitControl.Signature = "";
                returnVisitControl.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                returnVisitControl.Result = 1;
                str = JsonConvert.SerializeObject(returnVisitControl);
                strCmd = StringToHex(str);
            }
            SendMsg(strCmd, false, false);
        }

        public void StartReceive(object obj)
        {
            while (true)
            {
                try
                {
                    byte[] buffer = new byte[2048];

                    int lenght = server.Receive(buffer);
                    bool result = true;
                    List<byte> data = new List<byte>();
                    for (int j = 0; j < lenght; j++)
                    {

                        data.Add(buffer[j]);
                    }
                    ReceiveData message = AnalysisType(data);
                    if (message != null)
                    {
                        if (message.Command.ToUpper() == "KYL_VISIT_CONTROL")
                        {
                            LogHelper.Log("联动点亮:" + message.Data[0].ToString());
                            VISIT_CONTROL(message.Data[0].ToString(), message.DeviceID);
                        }
                        //联动授权
                        else if (message.Command.ToUpper() == "KYL_KEY_CONTROL")
                        {
                            LogHelper.Log("联动授权：" + message.Data[0].ToString());
                            KEY_CONTROL(message.Data[0].ToString(), message.DeviceID);
                        }
                        //电梯状态查询
                        else if (message.Command.ToUpper() == "KYL_STATUS_REQ")
                        {
                            ElevatorStatusReturnData elevatorStatusReturnData = new ElevatorStatusReturnData();
                            ElevatorInfoStatus elevatorInfoStatus = new ElevatorInfoStatus();
                            string strCmd = string.Empty;
                            string str = string.Empty;
                            try
                            {
                                LogHelper.Log("状态查询：" + message.Data[0].ToString());
                                QueryStatusDevice device = GetKYLSTATUSREQ(message.Data[0].ToString());
                                CurrentElevatorStatus currentElevatorStatus = new CurrentElevatorStatus();
                                serial.memoryCache.TryGetValue(1, out currentElevatorStatus);
                                elevatorInfoStatus.SubDeviceID = device.SubDeviceID;
                                if (currentElevatorStatus.Fault == 1)
                                {
                                    elevatorInfoStatus.State = "80";
                                }
                                else
                                {
                                    elevatorInfoStatus.State = "00";
                                }

                                if (currentElevatorStatus.Down == 1)
                                {
                                    elevatorInfoStatus.DoorDirection = "10";
                                }
                                else if (currentElevatorStatus.Up == 1)
                                {
                                    elevatorInfoStatus.DoorDirection = "01";
                                }
                                else
                                {
                                    elevatorInfoStatus.DoorDirection = "00";
                                }
                                elevatorInfoStatus.CurFloor = currentElevatorStatus.DisplayFloor;
                                elevatorStatusReturnData.Command = "KYL_STATUS_REQ";
                                elevatorStatusReturnData.DeviceID = device.SubDeviceID;
                                elevatorStatusReturnData.Seq = 1;
                                elevatorStatusReturnData.Signature = "";
                                elevatorStatusReturnData.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                elevatorStatusReturnData.Result = 0;
                                List<ElevatorInfoStatus> status_list = new List<ElevatorInfoStatus>();
                                status_list.Add(elevatorInfoStatus);
                                elevatorStatusReturnData.Data = status_list;
                                str = JsonConvert.SerializeObject(elevatorStatusReturnData);
                                string datazs = string.Format("{0} {1} {2} {3}", data[45].ToString("X").PadLeft(2, '0'), data[46].ToString("X").PadLeft(2, '0'), data[47].ToString("X").PadLeft(2, '0'), data[48].ToString("X").PadLeft(2, '0'));
                                strCmd = StringToHex(str);
                            }
                            catch
                            {
                                elevatorStatusReturnData.Command = "KYL_STATUS_REQ";
                                elevatorStatusReturnData.Seq = 1;
                                elevatorStatusReturnData.Signature = "";
                                elevatorStatusReturnData.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                                elevatorStatusReturnData.Result = 1;
                                str = JsonConvert.SerializeObject(elevatorStatusReturnData);
                                strCmd = StringToHex(str);
                            }
                            SendMsg(strCmd, false, false);
                        }
                        else
                        {

                            if (dic_data.ContainsKey(count))
                            {
                                dic_data.Remove(count);
                            }
                            dic_data.Add(count, data);
                        }
                    }

                }
                catch (Exception ex)
                {
                }

            }
        }


        public string ByteArrayToHexs(byte[] data)
        {
            if (data.Length <= 0) return "";
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < data.Length; i++)
            {
                sb.Append((data[i]).ToString("X2"));
            }
            string str = sb.ToString();
            return str;
        }
        public string Floor(int devid, int add, int count, int phy_floor, out int add_start)
        {
            string cmd = string.Empty;
            try
            {
                string strcmd = string.Empty;
                string strbyte = string.Empty;
                string strbit = string.Empty;

                if (phy_floor < 17)
                {
                    for (int i = 1; i < 17; i++)
                    {
                        if (phy_floor == i)
                        {
                            strbit = "1" + strbit;
                        }
                        else
                        {
                            strbit = "0" + strbit;
                        }
                    }
                }
                else if (phy_floor > 17 && phy_floor < 33)
                {
                    add = add + 1;
                    for (int i = 17; i < 33; i++)
                    {
                        if (phy_floor == i)
                        {
                            strbit = "1" + strbit;
                        }
                        else
                        {
                            strbit = "0" + strbit;
                        }
                    }
                }
                else if (phy_floor > 32 && phy_floor < 49)
                {
                    add = add + 2;
                    for (int i = 33; i < 49; i++)
                    {
                        if (phy_floor == i)
                        {
                            strbit = "1" + strbit;
                        }
                        else
                        {
                            strbit = "0" + strbit;
                        }
                    }
                }
                else if (phy_floor > 48 && phy_floor < 65)
                {
                    add = add + 3;
                    for (int i = 49; i < 65; i++)
                    {
                        if (phy_floor == i)
                        {
                            strbit = "1" + strbit;
                        }
                        else
                        {
                            strbit = "0" + strbit;
                        }
                    }
                }
                else if (phy_floor > 64 && phy_floor < 81)
                {
                    add = add + 4;
                    for (int i = 65; i < 81; i++)
                    {
                        if (phy_floor == i)
                        {
                            strbit = "1" + strbit;
                        }
                        else
                        {
                            strbit = "0" + strbit;
                        }
                    }
                }
                add_start = add;
                strcmd = Convert.ToInt32(strbit.Substring(0, 8), 2).ToString("X").PadLeft(2, '0') + " " + Convert.ToInt32(strbit.Substring(8, 8), 2).ToString("X").PadLeft(2, '0');

                string addhex = (add - 1).ToString("X").PadLeft(4, '0');
                string numhex = count.ToString("X").PadLeft(4, '0');
                string bytecount = (2 * count).ToString("X").PadLeft(2, '0');
                strcmd = "01 10 " + addhex.Substring(0, 2) + " " + addhex.Substring(2, 2) + " " + numhex.Substring(0, 2) + " " + numhex.Substring(2, 2) + " " + bytecount + " " + strcmd;
                byte[] data = ToBytesSendDate(strcmd);
                byte[] crc = Crc18(data);
                strcmd += " " + crc[1].ToString("X").PadLeft(2, '0') + " " + crc[0].ToString("X").PadLeft(2, '0');
                cmd = strcmd;
                return cmd;
            }
            catch (Exception ex)
            {
                logPrint.Log("命令解析异常");
                add_start = add;
                return "";
            }
        }

        public byte[] Crc18(byte[] buffer, int start = 0, int len = 0)
        {
            if (buffer == null || buffer.Length == 0) return null;
            if (start < 0) return null;
            if (len == 0) len = buffer.Length - start;
            int length = start + len;
            if (length > buffer.Length) return null;
            ushort crc = 0xFFFF;// Initial value
            for (int i = start; i < length; i++)
            {
                crc ^= buffer[i];
                for (int j = 0; j < 8; j++)
                {
                    if ((crc & 1) > 0)
                        crc = (ushort)((crc >> 1) ^ 0xA001);// 0xA001 = reverse 0x8005
                    else
                        crc = (ushort)(crc >> 1);
                }
            }
            byte[] ret = BitConverter.GetBytes(crc);
            Array.Reverse(ret);
            return ret;
        }

        public byte[] ToBytesSendDate(string str)
        {
            List<byte> result = new List<byte>();
            if (str.Contains(" "))
            {
                string[] strs = str.Trim().Split(' ');
                foreach (string s in strs)
                {
                    result.Add(Convert.ToByte(s.Trim(), 16));
                }
            }
            else
            {
                result.Add(Convert.ToByte(str, 16));
            }
            return result.ToArray();
        }
        public static string Reverse(string str)
        {
            char[] arr = str.ToCharArray();
            Array.Reverse(arr);
            return new string(arr);
        }

        public string ToHexs(byte[] data)
        {
            if (data.Length <= 0) return "";
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < data.Length; i++)
            {
                sb.Append(data[i].ToString("X2"));
                sb.Append(" ");
            }
            string str = sb.ToString();
            return str.Substring(0, str.Length - 1);
        }
        #endregion

        public DevInfo GetDevInfo()
        {
            string strSql = "SELECT * FROM devinfo";
            CommFN<DevInfo> fn = new CommFN<DevInfo>();
            return fn.GetData(strSql);
        }

        #region 数据解析  

        /// <summary>
        /// 解析类型
        /// </summary>
        public ReceiveData AnalysisType(List<byte> data1)
        {
            ReceiveData message;
            try
            {
                //List<byte> data = data1.GetRange(57, data1.Count - 57);
                string result = string.Empty;
                result = Encoding.GetEncoding("utf-8").GetString(data1.ToArray(), 0, data1.Count);
                message = JsonConvert.DeserializeObject<ReceiveData>(result);
            }
            catch
            {
                return null;
            }
            return message;
        }

        /// <summary>
        /// 凭证解析
        /// </summary>
        public CardInfo GetVoucherInfo(string data)
        {
            CardInfo cardInfo;
            try
            {
                cardInfo = JsonConvert.DeserializeObject<CardInfo>(data);
            }
            catch
            {
                logPrint.Log("凭证为空");
                return null;
            }
            return cardInfo;
        }

        /// <summary>
        /// 参数设置解析
        /// </summary>
        public ParameterSet GetParameterSet(string data)
        {
            ParameterSet para;
            try
            {
                para = JsonConvert.DeserializeObject<ParameterSet>(data);
            }
            catch
            {
                return null;
            }
            return para;
        }

        /// <summary>
        /// 状态查询解析
        /// </summary>
        public StatusQuery GetCarStatusQuery(string data)
        {
            StatusQuery status;
            try
            {
                status = JsonConvert.DeserializeObject<StatusQuery>(data);
            }
            catch
            {
                return null;
            }
            return status;
        }

        /// <summary>
        /// 命令解析
        /// </summary>
        public CmdMessage GetCmdInfo(string data)
        {
            CmdMessage message;
            try
            {
                message = JsonConvert.DeserializeObject<CmdMessage>(data);
            }
            catch
            {
                return null;
            }
            return message;
        }

        /// <summary>
        /// 联动点亮解析
        /// </summary>
        public VisitControl GetVisitControl(string data)
        {
            VisitControl visitControl;
            try
            {
                visitControl = JsonConvert.DeserializeObject<VisitControl>(data);
            }
            catch
            {
                logPrint.Log("凭证为空");
                return null;
            }
            return visitControl;
        }


        /// <summary>
        /// 查询电梯状态解析
        /// </summary>
        public QueryStatusDevice GetKYLSTATUSREQ(string data)
        {
            QueryStatusDevice queryStatusDevice;
            try
            {
                queryStatusDevice = JsonConvert.DeserializeObject<QueryStatusDevice>(data);
            }
            catch
            {
                logPrint.Log("查询电梯为空");
                return null;
            }
            return queryStatusDevice;
        }

        /// <summary>
        /// 解析回复数据
        /// </summary>
        public InitReplayData AnalysisReplay(List<byte> data1)
        {
            InitReplayData message;
            try
            {
                //List<byte> data = data1.GetRange(57, data1.Count - 57);
                string result = string.Empty;
                result = Encoding.GetEncoding("utf-8").GetString(data1.ToArray(), 0, data1.Count);
                message = JsonConvert.DeserializeObject<InitReplayData>(result);
            }
            catch
            {
                return null;
            }
            return message;
        }

        #endregion

        #region 发送消息、发送后回复消息解析
        public bool SendMsg(string str, bool isinitiative, bool isRegCmd)
        {
            lock (sendlocker)
            {
                try
                {
                    string senddata = string.Format(@"{0}", str);
                    bool result = false;
                    while (!result)
                    {
                        if (server.Connected == true)
                        {
                            if (isReg)
                            {
                                try
                                {
                                    server.Send(HexStringToByteArray(senddata));
                                }
                                catch
                                {
                                    isReg = false;
                                    return false;
                                }
                                if (isinitiative)
                                {
                                    if (count < 2147483647)
                                    {
                                        count++;
                                    }
                                    else
                                    {
                                        count = 1;
                                    }
                                }
                                return true;
                            }
                            else
                            {
                                if (isRegCmd)
                                {
                                    try
                                    {
                                        server.Send(HexStringToByteArray(senddata));
                                    }
                                    catch
                                    {
                                        isReg = false;
                                        return false;
                                    }
                                    if (isinitiative)
                                    {
                                        if (count < 2147483647)
                                        {
                                            count++;
                                        }
                                        else
                                        {
                                            count = 1;
                                        }
                                    }
                                    return true;
                                }
                                else
                                {
                                    return false;
                                }
                            }
                        }
                        else
                        {
                            if (!firstReg)
                            {
                                t.Close();
                                if (isreport)
                                {
                                    reporttimer.Close();
                                }
                            }
                            isReg = false;
                            if (ConnectToHD(devinfo.serverIP, devinfo.serverport))
                            {
                                if (Init())
                                {
                                    isReg = true;
                                }
                            }
                        }
                    }
                    return true;
                }
                catch (Exception ex)
                {
                    return false;
                }
            }
        }

        /* public bool SendMsg(string str, bool isinitiative, bool isRegCmd)
         {
             lock (sendlocker)
             {
                 try
                 {
                     string senddata = string.Format(@"{0}", str);
                     bool result = false;
                     while (!result)
                     {
                         if (server.Connected == true)
                         {
                             try
                             {
                                 server.Send(HexStringToByteArray(senddata));
                             }
                             catch
                             {
                                 isReg = false;
                                 return false;
                             }
                             return true;
                         }
                     }
                     return true;
                 }
                 catch (Exception ex)
                 {
                     return false;
                 }
             }
         }*/

        public static byte[] HexStringToByteArray(string s)
        {
            s = s.Replace(" ", "");
            byte[] buffer = new byte[s.Length / 2];
            for (int i = 0; i < s.Length; i += 2)
                buffer[i / 2] = (byte)Convert.ToByte(s.Substring(i, 2), 16);
            return buffer;
        }

        #endregion

        public string GetMACIp()
        {
            //本地计算机网络连接信息
            IPGlobalProperties computerProperties = IPGlobalProperties.GetIPGlobalProperties();
            //获取本机所有网络连接
            NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();

            if (nics == null || nics.Length < 1)
            {
                return "";
            }

            var MACIp = "";
            foreach (NetworkInterface adapter in nics)
            {
                var adapterName = adapter.Name;

                var adapterDescription = adapter.Description;
                var NetworkInterfaceType = adapter.NetworkInterfaceType;
                if (adapterName == "eth0")
                {
                    PhysicalAddress address = adapter.GetPhysicalAddress();
                    byte[] bytes = address.GetAddressBytes();
                    for (int i = 0; i < bytes.Length; i++)
                    {
                        MACIp += bytes[i].ToString("X2");

                        if (i != bytes.Length - 1)
                        {
                            MACIp += "-";
                        }
                    }
                }
            }

            return MACIp;
        }

        public string CRCCalc(string data)
        {
            string[] datas = data.Split(' ');
            List<byte> bytedata = new List<byte>();

            foreach (string str in datas)
            {
                bytedata.Add(byte.Parse(str, System.Globalization.NumberStyles.AllowHexSpecifier));
            }
            byte[] crcbuf = bytedata.ToArray();
            //计算并填写CRC校验码
            int crc = 0xffff;
            int len = crcbuf.Length;

            for (int j = 0; j < len; j++)
            {
                crc = ((crc >> 8) | (crc << 8)) & 0xffff;
                crc ^= (crcbuf[j] & 0xff);
                crc ^= ((crc & 0xff) >> 4);
                crc ^= (crc << 12) & 0xffff;
                crc ^= ((crc & 0xff) << 5) & 0xffff;
            }
            crc = crc & 0xffff;

            string[] redata = new string[2];
            redata[1] = Convert.ToString((byte)((crc >> 8) & 0xff), 16);
            redata[0] = Convert.ToString((byte)((crc & 0xff)), 16);
            string a = redata[1].ToString().PadLeft(2, '0') + " " + redata[0].ToString().PadLeft(2, '0');
            return a.ToUpper();
        }

        #region 设备注册、目录查询、子设备上报、心跳上报

        public bool DevReister(DevInfo devinfo)
        {
            try
            {
                int packnum = count;
                if (!string.IsNullOrEmpty(devinfo.serverIP) && devinfo.serverport > 0)
                {
                    RegInfo data1 = new RegInfo();
                    data1.Type = 1;
                    data1.Version = serial.getversion();
                    data1.SN = "00000001";
                    //data1.mac = devinfo.mac;
                    //data1.deviceID = "1011" + "2020" + data1.mac.Replace("-", "");
                    //logPrint.Log(data1.deviceID);
                    //devid = data1.deviceID;
                    devid = "10112020" + GetLocalMac().ToUpper();
                    MessageData msgdata = new MessageData();
                    msgdata.Seq = 1;
                    /* if (data1.mac.Contains("-"))
                     {
                         data1.mac.Replace("-", "");
                     }*/
                    // msgdata.DeviceID = "1011" + "2020" + data1.mac;
                    msgdata.DeviceID = devid;
                    msgdata.Command = "DEV_REGISTER";
                    msgdata.Signature = "";
                    msgdata.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                    List<RegInfo> list = new List<RegInfo>();
                    list.Add(data1);
                    msgdata.Data = list;
                    string str = JsonConvert.SerializeObject(msgdata);
                    string zs = IntToHex(packnum).PadLeft(8, '0');
                    string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                    string strCmd = StringToHex(str);
                    /* int num = strCmd.Split(' ').Length;
                     string datalength = IntToHex(num).PadLeft(8, '0');
                     string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                     string crc = CRCCalc(strCmd);
                     string device_send = msgdata.DeviceID;
                     if (device_send.Length < 20)
                     {
                         device_send = device_send.PadLeft(20, '0');
                     }
                     strCmd = "4A 4D 58 4D " + StringToHex(device_send) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;
 */
                    return SuccessDev(strCmd, "DEV_REGISTER");
                }
                return false;
            }
            catch (Exception e)
            {
                logPrint.Log(e.ToString());
                return false;
            }
        }

        public string GetLocalIP()
        {
            string localIP = string.Empty;
            try
            {
                using (Socket socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, 0))
                {
                    socket.Connect("8.8.8.8", 65530);
                    IPEndPoint endPoint = socket.LocalEndPoint as IPEndPoint;
                    localIP = endPoint.Address.ToString();
                }
                return localIP;
            }
            catch
            {
                return "";
            }
        }
        public string GetLocalMac()
        {
            string macAddress = "";
            try
            {
                foreach (NetworkInterface nic in NetworkInterface.GetAllNetworkInterfaces())
                {
                    if (nic.OperationalStatus == OperationalStatus.Up)
                    {
                        macAddress = nic.GetPhysicalAddress().ToString();
                        IPInterfaceProperties ipProperties = nic.GetIPProperties();
                        UnicastIPAddressInformation curIP = ipProperties.UnicastAddresses[0];
                        string ip = curIP.Address.ToString();
                        string mask = curIP.IPv4Mask.ToString();
                        string server = ipProperties.GatewayAddresses[0].Address.ToString();
                        break;
                    }
                }
                return macAddress;
            }
            catch
            {
                return "";
            }
        }

        public bool SubDevReport(DevInfo devinfo)
        {
            try
            {
                int packnum = count;
                if (!string.IsNullOrEmpty(devinfo.serverIP) && devinfo.serverport > 0)
                {
                    HDRegInfo data1 = new HDRegInfo();
                    string liftid = string.Empty;

                    data1.mac = devinfo.mac;
                    data1.ip = devinfo.localIP;
                    data1.mask = devinfo.mask;

                    liftid = devinfo.liftid.ToString("X").PadLeft(4, '0');
                    data1.manufacturer = "3063";

                    data1.Version = serial.getversion();
                    data1.deviceID = "3063" + data1.mac.Replace("-", "") + liftid;
                    subdevid = data1.deviceID;
                    HDMessageData msgdata = new HDMessageData();
                    msgdata.Command = "COM_UPLOAD_SUB_DEV";
                    List<HDRegInfo> list = new List<HDRegInfo>();
                    list.Add(data1);
                    msgdata.Data = list;
                    string str = JsonConvert.SerializeObject(msgdata);
                    string zs = IntToHex(packnum).PadLeft(8, '0'); ;
                    string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                    string strCmd = StringToHex(str);
                    int num = strCmd.Split(' ').Length;
                    string datalength = IntToHex(num).PadLeft(8, '0');
                    string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                    string crc = CRCCalc(strCmd);
                    strCmd = "48 44 58 4D " + StringToHex(data1.deviceID) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;

                    return SendMsg(strCmd, true, false);
                }
                return false;
            }
            catch
            {
                return false;
            }
        }

        public bool SuccessDev(string strCmd, string type)
        {
            int sendcount = 0;
            if (server != null)
            {
                bool result = SendMsg(strCmd, true, true);

                if (result)
                {
                    //  logPrint.Log("注册发送成功");
                    while (true)
                    {
                        if (ReceiveData(type))
                        {
                            logPrint.Log("设备初始化成功");
                            return true;
                        }
                        sendcount++;
                        if (sendcount > 10)
                        {
                            return false;
                        }
                        Wait(1000);
                        //Thread.Sleep(1000);
                    }
                }
                else
                {
                    Wait(10000);
                    //Thread.Sleep(10000);
                }
            }
            return false;
        }

        public bool SuccessHeart(string strCmd, string type)
        {
            int count = 0;
            if (server != null)
            {
                bool result = SendMsg(strCmd, true, false);
                if (result)
                {
                    while (count < 3)
                    {
                        if (ReceiveData(type))
                        {
                            logPrint.Log("心跳接收成功");
                            return true;
                        }
                        Wait(100);
                        // Thread.Sleep(100);
                        count++;
                    }
                    return false;
                }
                else
                {
                    return false;
                }
            }
            return false;
        }

        public bool Wait(int second)
        {
            try
            {
                DateTime startTime = DateTime.Now;
                while (true)
                {
                    TimeSpan secondSpan = new TimeSpan(DateTime.Now.Ticks - startTime.Ticks);
                    if (secondSpan.TotalMilliseconds > second)
                    {
                        break;
                    }
                }
                return true;
            }
            catch
            {
                return false;
            }
        }

        public bool CheckHeart()
        {
            try
            {
                int packnum = count;
                //SendData msgdata = new SendData();
                HeartInfo data1 = new HeartInfo();
                data1.Type = 1;
                data1.Version = serial.getversion();
                //devid = data1.deviceID;
                HeartData msgdata = new HeartData();
                //data1.mac = devinfo.mac;
                msgdata.Seq = 1;
                msgdata.DeviceID = devid;
                msgdata.Command = "DEV_HEARTBEAT";
                msgdata.Signature = "";
                msgdata.TimeStamp = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                List<HeartInfo> list = new List<HeartInfo>();
                list.Add(data1);
                msgdata.Data = list;
                string str = JsonConvert.SerializeObject(msgdata);
                string zs = IntToHex(packnum).PadLeft(8, '0');
                string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                string strCmd = StringToHex(str);
                /* int num = strCmd.Split(' ').Length;
                 string datalength = IntToHex(num).PadLeft(8, '0');
                 string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                 string crc = CRCCalc(strCmd);
                 string device_send = msgdata.DeviceID;
                 if (device_send.Length < 20)
                 {
                     device_send = device_send.PadLeft(20, '0');
                 }
                 strCmd = "4A 4D 58 4D " + StringToHex(device_send) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;
 */
                return SuccessHeart(strCmd, "DEV_HEARTBEAT");

            }
            catch (Exception e)
            {
                return false;
            }
        }

        public bool ReceiveData(string messagetype)
        {
            foreach (var item in dic_data)
            {
                try
                {
                    InitReplayData initReplay = new InitReplayData();
                    if (item.Value.Count != 0)
                    {
                        initReplay = AnalysisReplay(item.Value);
                        if (initReplay != null)
                        {
                            if (initReplay.Command == messagetype && initReplay.Result == 0)
                            {
                                dic_data.Remove(item.Key);
                                return true;
                            }
                        }
                    }
                }
                catch
                {
                    continue;
                }
            }

            return false;

        }
        #endregion

        #region 凭证操作

        public bool InsertVoucher(CardInfo cardInfo)
        {
            /*            if (cardInfo.UserType == 0)
                        {
                            cardInfo.UserType = 2;
                        }*/
            string strSql = string.Format(@"INSERT INTO cardinfo(cardID,StartTime,OverTime,subDeviceID,UserType,CredenceType,username,UUID,elevatorAuthFloor)VALUES('{0}','{1}','{2}','{3}',{4},{5},'{6}','{7}','{8}')", cardInfo.credenceNo, cardInfo.startTime, cardInfo.endTime, cardInfo.subDeviceID, 3, cardInfo.CredenceType, "", cardInfo.userID, string.Join(",", cardInfo.elevatorAuthFloor));
            CommFN<CardInfo> fn = new CommFN<CardInfo>();
            return fn.ExecFN(strSql);
        }

        public VoucherInfo QueryVoucher(CardInfo cardInfo)
        {
            string strSql = string.Format(@"SELECT * FROM cardinfo WHERE UUID='{0}'", cardInfo.userID);
            CommFN<VoucherInfo> fn = new CommFN<VoucherInfo>();
            return fn.GetData(strSql);
        }

        public bool UpdateVoucher(CardInfo cardInfo)
        {
            string strSql = string.Format(@"UPDATE cardinfo SET cardID='{0}',StartTime='{1}',OverTime='{2}',subDeviceID='{3}',UserType='{4}',CredenceType={5},username='{6}',elevatorAuthFloor='{7}' WHERE UUID='{8}'", cardInfo.credenceNo, cardInfo.startTime, cardInfo.endTime, cardInfo.subDeviceID, 3, cardInfo.CredenceType, "", string.Join(",", cardInfo.elevatorAuthFloor), cardInfo.userID);
            CommFN<VoucherInfo> fn = new CommFN<VoucherInfo>();
            return fn.ExecFN(strSql);
        }

        public bool DelVoucher(CardInfo cardInfo)
        {
            string strSql = string.Format(@"DELETE FROM cardinfo WHERE UUID='{0}'", cardInfo.userID);
            CommFN<VoucherInfo> fn = new CommFN<VoucherInfo>();
            return fn.ExecFN(strSql);
        }

        public bool DelAllTypeVoucher(int type)
        {
            string strSql = "DELETE FROM cardinfo";
            CommFN<VoucherInfo> fn = new CommFN<VoucherInfo>();
            return fn.ExecFN(strSql);
        }

        #endregion

        #region 参数操作
        public bool UpdateParameter(ParameterSet para)
        {
            string strSql = string.Format(@"UPDATE devinfo SET intervalTime={0},ntpserver='{1}'", Convert.ToInt32(para.intervalTime), para.ntpServer);
            CommFN<CardInfo> fn = new CommFN<CardInfo>();
            return fn.ExecFN(strSql);
        }
        #endregion

        /// <summary>
        /// 乘梯事件上报
        /// </summary>
        public void IncidentReporting(Incident incident)
        {
            try
            {
                incident.deviceID = subdevid;
                IncidentMessage replay = new IncidentMessage();
                List<Incident> list = new List<Incident>();
                list.Add(incident);
                replay.Command = "FAC_ELEVATOR_RECORD";
                replay.Data = list;
                string str = JsonConvert.SerializeObject(replay);
                string zs = IntToHex(count).PadLeft(8, '0'); ;
                string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                string strCmd = StringToHex(str);
                int num = strCmd.Split(' ').Length;
                string datalength = IntToHex(num).PadLeft(8, '0');
                string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                string crc = CRCCalc(strCmd);
                strCmd = "48 44 58 4D " + StringToHex(devid) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;

                SendMsg(strCmd, true, false);
            }
            catch
            {

            }
        }

        /// <summary>
        /// 轿厢状态上报
        /// </summary>
        public void CarStatusReport(object source, ElapsedEventArgs e)
        {
            lock (carstatuslocker)
            {
                ElevatorPoint point;
                serial.memoryCache.TryGetValue(devinfo.liftid, out point);
                CarStatus carStatus = new CarStatus();
                Data data = new Data();
                carStatus.Data = data;
                List<ElevatorStatus> list = new List<ElevatorStatus>();
                ElevatorStatus newstatus = new ElevatorStatus();
                newstatus.deviceID = subdevid;
                newstatus.carID = devinfo.liftid.ToString().PadLeft(2, '0');
                newstatus.physicalfloor = point.physicalfloor;
                newstatus.displayfloor = point.Showfloor;
                if (point.up == 1)
                {
                    newstatus.status = "01";
                }
                else if (point.down == 1)
                {
                    newstatus.status = "02";
                }
                else if (point.up == 0 && point.down == 0)
                {
                    newstatus.status = "00";
                }

                if (point.behinddooropening == 1)
                {
                    newstatus.doorStatus = "10";
                }
                else if (point.behinddooropened == 1)
                {
                    newstatus.doorStatus = "11";
                }
                else if (point.behinddoorcloseing == 1)
                {
                    newstatus.doorStatus = "12";
                }
                else if (point.behinddoorclosed == 1)
                {
                    newstatus.doorStatus = "13";
                }

                newstatus.errorStatus = point.falut;
                newstatus.errorMessage = "";
                newstatus.fireCtrlStatus = point.fire;

                list.Add(newstatus);

                carStatus.Command = "FAC_UPLOAD_BA_STATUS";
                carStatus.Data.statusList = list;
                carStatus.Data.timestamp = DateTime.Now.ToString("yyyy-MM-dd hh:mm:ss");
                string str = JsonConvert.SerializeObject(carStatus);
                string zs = IntToHex(count).PadLeft(8, '0'); ;
                string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                string strCmd = StringToHex(str);
                int num = strCmd.Split(' ').Length;
                string datalength = IntToHex(num).PadLeft(8, '0');
                string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                string crc = CRCCalc(strCmd);
                strCmd = "48 44 58 4D " + StringToHex(devid) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;
                //SendMsg(strCmd, true, false);
            }
        }

        /// <summary>
        /// 电梯设备状态上报
        /// </summary>
        public void ElevatorDevReport(Device dev)
        {
            if (!string.IsNullOrEmpty(subdevid))
            {
                dev.deviceID = subdevid;
                List<Device> list = new List<Device>();
                list.Add(dev);
                ElevatorEquipment elevator = new ElevatorEquipment();
                elevator.Command = "FAC_UPLOAD_DEV_STATUS";
                elevator.Data = list;
                string str = JsonConvert.SerializeObject(elevator);
                string zs = IntToHex(count).PadLeft(8, '0'); ;
                string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
                string strCmd = StringToHex(str);
                int num = strCmd.Split(' ').Length;
                string datalength = IntToHex(num).PadLeft(8, '0');
                string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
                string crc = CRCCalc(strCmd);
                strCmd = "48 44 58 4D " + StringToHex(devid) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;
                SendMsg(strCmd, true, false);
            }


        }

        /// <summary>
        /// 批量查询
        /// </summary>
        public bool QueryAllCarStatus()
        {
            CarStatus carStatus = new CarStatus();
            ElevatorPoint point = new ElevatorPoint();
            memoryCache = serial.GetStatusMemory();
            memoryCache.TryGetValue(devinfo.liftid, out point);
            ElevatorStatus status = new ElevatorStatus();
            if (point != null)
            {
                status.deviceID = subdevid;
                status.carID = devinfo.liftid.ToString().PadLeft(2, '0');
                status.physicalfloor = point.physicalfloor;
                status.displayfloor = point.Showfloor;
                if (point.up == 1)
                {
                    status.status = "01";
                }
                else if (point.down == 1)
                {
                    status.status = "02";
                }
                else
                {
                    status.status = "00";
                }

                if (point.frontdooropening == 1)
                {
                    status.doorStatus = "10";
                }
                else if (point.frontdooropened == 1)
                {
                    status.doorStatus = " 11";
                }
                else if (point.frontdoorcloseing == 1)
                {
                    status.doorStatus = " 12";
                }
                else if (point.frontdoorclosed == 1)
                {
                    status.doorStatus = " 13";
                }

                if (point.falut == 1)
                {
                    status.errorStatus = 1;
                }
                else
                {
                    status.errorStatus = 0;
                }
            }

            carStatus.Command = "FAC_LIFT_BA_STATUS";
            carStatus.Data.statusList.Add(status);
            string str = JsonConvert.SerializeObject(carStatus);
            string zs = IntToHex(count).PadLeft(8, '0'); ;
            string datazs = zs.Substring(0, 2) + " " + zs.Substring(2, 2) + " " + zs.Substring(4, 2) + " " + zs.Substring(6, 2);
            string strCmd = StringToHex(str);
            int num = strCmd.Split(' ').Length;
            string datalength = IntToHex(num).PadLeft(8, '0');
            string length = datalength.Substring(0, 2) + " " + datalength.Substring(2, 2) + " " + datalength.Substring(4, 2) + " " + datalength.Substring(6, 2);
            string crc = CRCCalc(strCmd);
            strCmd = "48 44 58 4D " + StringToHex(devid) + " " + StringToHex("00000000000000000000") + " 00 " + datazs + " " + length + " 00 00 " + crc + " " + strCmd;
            if (SendMsg(strCmd, true, false))
            {
                return true;
            }
            else
            {
                return false;
            }
        }

        #region 连接金茂平台、设备注册、子设备上报、目录查询、心跳上报

        public void HDConnect()
        {
            try
            {
                devinfo.mac = GetLocalMac();
                //devinfo.mac = GetMACIp();
                devinfo.localIP = GetLocalIP();
                // devinfo.mask = GetLocalNetInfo().Mask;
                Task task = new Task(async () =>
                {
                    if (token.IsCancellationRequested)
                    {
                        return;
                    }
                    resetEvent.WaitOne();
                    //do something
                    PowerOnConnection();

                }, token);
                task.Start();
            }
            catch (Exception e)
            {
                LogHelper.Log(e.ToString());
            }
        }

        public void PowerOnConnection()
        {
            try
            {
                if (ConnectToHD(devinfo.serverIP, devinfo.serverport))
                {
                    logPrint.Log("连接金茂系统成功");
                    Init();
                }
            }
            catch
            {

            }
        }

        public bool ConnectToHD(string serverip, int port)
        {
            bool result = false;
            while (!result)
            {
                result = ConnectServer(serverip, port);
            }

            return result;
        }

        public bool Register(DevInfo devInfo)
        {
            bool result = false;
            hdstatus = 1;
            while (!result)
            {
                result = DevReister(devInfo);
            }
            return result;
        }

        public bool SubReportt(DevInfo devInfo)
        {
            bool result = false;
            while (!result)
            {
                //result = SubDevReport(devInfo);
            }
            return result;
        }

        public bool Init()
        {
            if (Register(devinfo))
            {
                Equipment equipment = new Equipment();
                equipment.devtype = "金茂平台";
                equipment.state = 0;
                equipment.reason = "注册成功";
                equipment.actiontime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                InsertEquipment(equipment);

                isReg = true;
                //开启心跳上报定时服务
                HeartReport();

                /*if (SubReportt(devinfo))
                {
                    //开启轿厢状态上报
                    if (reporttime > 0)
                    {
                        CarStatusServer();
                    }
                    return true;
                }*/
            }
            return false;
        }

        public void HeartReport()
        {
            try
            {
                heartcount = 0;
                heart();
                t = new System.Timers.Timer(60000);//实例化Timer类，设置间隔时间为200毫秒；

                t.Elapsed += new ElapsedEventHandler(Check);//到达时间的时候执行事件；

                t.AutoReset = true;//设置是执行一次（false）还是一直执行(true)；

                t.Enabled = true;//是否执行System.Timers.Timer.Elapsed事件；
            }
            catch (Exception ex)
            {
                logPrint.Log("报错信息：" + ex.ToString());
                //throw;
            }
        }

        public void Check(object source, ElapsedEventArgs e)
        {
            try
            {
                hdstatus = 2;
                logPrint.Log("心跳间隔一分钟发送");
                if (CheckHeart())
                {
                    heartcount = 0;
                }
                else
                {
                    if (heartcount >= 2)
                    {
                        Equipment equipment = new Equipment();
                        equipment.devtype = "金茂平台";
                        equipment.state = 1;
                        equipment.actiontime = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");
                        equipment.reason = "心跳接收三次失败";
                        InsertEquipment(equipment);
                        logPrint.Log("心跳接收三次失败，重新注册");
                        t.Close();
                        if (isreport)
                        {
                            reporttimer.Close();
                        }
                        Init();
                    }
                    else
                    {
                        heartcount++;
                    }
                }
            }
            catch
            {
                heartcount++;
            }
        }

        public void InsertEquipment(Equipment equipment)
        {
            DeviceDAL da = new DeviceDAL();
            da.InsertEquipment(equipment);
        }

        public void InsertModeRecord(ModeRecord modeRecord)
        {
            DeviceDAL da = new DeviceDAL();
            da.InsertModeRecord(modeRecord);
        }

        public void heart()
        {
            logPrint.Log("心跳第一次发送");
            try
            {
                hdstatus = 2;

                if (!CheckHeart())
                {
                    heartcount++;
                }
            }
            catch
            {
                heartcount++;
            }
        }

        #endregion

        public string GetLocalIp()
        {
            try
            {
                //本地计算机网络连接信息
                IPGlobalProperties computerProperties = IPGlobalProperties.GetIPGlobalProperties();
                //获取本机所有网络连接
                NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();

                if (nics == null || nics.Length < 1)
                {
                    return "";
                }
                foreach (NetworkInterface adapter in nics)
                {
                    var adapterName = adapter.Name;
                    //LogHelper.Log(adapterName);
                    if (adapterName == "eth0")
                    {
                        //LogHelper.Log(adapter.GetIPProperties().UnicastAddresses[0].Address.ToString());
                        return adapter.GetIPProperties().UnicastAddresses[0].Address.ToString();
                    }
                }
                return "";

            }
            catch (Exception e)
            {
                return "";
            }
        }

        public string GetLocalMask()
        {
            try
            {
                //本地计算机网络连接信息
                IPGlobalProperties computerProperties = IPGlobalProperties.GetIPGlobalProperties();
                //获取本机所有网络连接
                NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();

                if (nics == null || nics.Length < 1)
                {
                    return "";
                }
                foreach (NetworkInterface adapter in nics)
                {
                    var adapterName = adapter.Name;
                    if (adapterName == "eth0")
                    {
                        return adapter.GetIPProperties().UnicastAddresses[0].IPv4Mask.ToString();
                    }
                }
                return "";

            }
            catch (Exception e)
            {
                return "";
            }
        }

        public NetInfo GetLocalNetInfo()
        {
            NetInfo netInfo = new NetInfo();
            if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux))
            {
                StreamReader reader = new StreamReader(@"/etc/dhcpcd.conf", Encoding.Default);
                string theReply = reader.ReadToEnd();
                reader.Close();
                Regex addressRegex = new Regex(@"(?<ip>([^\w\s]+|\s*)static\s*ip_address=\d+.\d+.\d+.\d+/\d+)\s*");
                Regex ipRegex = new Regex(@"=\s*(?<ip>\d+.\d+.\d+.\d+)\s*");
                Regex maskReg = new Regex(@"=\s*\d+.\d+.\d+.\d+/(?<mask>\d+)\s*");
                MatchCollection addressCollection = addressRegex.Matches(theReply);
                for (int i = 0; i < addressCollection.Count; i++)
                {
                    string str = addressCollection[i].Groups["ip"].Value.Trim();
                    if (!str.Contains("#"))
                    {
                        string ip = ipRegex.Matches(str)[0].Groups["ip"].Value.Trim();
                        netInfo.IP = ip;
                        int mask = Convert.ToInt32(maskReg.Matches(str)[0].Groups["mask"].Value.Trim());
                        netInfo.Mask = GetMask(mask);
                    }
                }
            }
            else
            {
                try
                {
                    string name = Dns.GetHostName();
                    IPAddress[] ipadrlist = Dns.GetHostAddresses(name);
                    foreach (IPAddress ipa in ipadrlist)
                    {
                        if (ipa.AddressFamily == AddressFamily.InterNetwork)
                        {
                            netInfo.IP = ipa.ToString();
                            netInfo.Mask = "255.255.255.0";
                        }
                    }
                    /*//本地计算机网络连接信息
                    IPGlobalProperties computerProperties = IPGlobalProperties.GetIPGlobalProperties();
                    //获取本机所有网络连接
                    NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();

                    if (nics == null || nics.Length < 1)
                    {
                        return netInfo;
                    }
                    foreach (NetworkInterface adapter in nics)
                    {
                        var adapterName = adapter.Name;
                        //LogHelper.Log(adapterName);
                        if (adapterName == "本地连接")
                        {
                            netInfo.IP = adapter.GetIPProperties().UnicastAddresses[0].Address.ToString();
                            netInfo.Mask = adapter.GetIPProperties().UnicastAddresses[0].IPv4Mask.ToString();
                        }
                    }*/

                }
                catch (Exception e)
                {
                    return netInfo;
                }
            }

            return netInfo;
        }

        public string GetMask(int value)
        {
            try
            {
                string str = string.Empty;
                for (int i = 0; i < value; i++)
                {
                    str += "1";
                }
                str = str.PadRight(32, '0');
                string a = Convert.ToInt32(str.Substring(0, 8), 2).ToString() + "." + Convert.ToInt32(str.Substring(8, 8), 2).ToString() + "." + Convert.ToInt32(str.Substring(16, 8), 2).ToString() + "." + Convert.ToInt32(str.Substring(24, 8), 2).ToString();
                return a;
            }
            catch
            {
                return "0.0.0.0";
            }
        }

        public int hd()
        {
            return hdstatus;
        }

        public void CarStatusServer()
        {
            try
            {
                reporttimer = new System.Timers.Timer(Convert.ToDouble(reporttime));

                reporttimer.Elapsed += new ElapsedEventHandler(CarStatusReport);//到达时间的时候执行事件；

                reporttimer.AutoReset = true;//设置是执行一次（false）还是一直执行(true)；

                reporttimer.Enabled = true;//是否执行System.Timers.Timer.Elapsed事件；
                isreport = true;
            }
            catch (Exception ex)
            {
                logPrint.Log("报错信息：" + ex.ToString());
            }
        }

        public ElevatorStatusInfo GetElevatorStatusInfo()
        {
            return ElevatorStatusInfo;
        }
    }
}
